<?php
/*
 * class CT_WARP
 * 系统包裹函数
*/

class CT_WARP {
	
	function file_exists($file, $type = 'sys') {
		switch ($type) {
			case 'ctl':
				return file_exists(__APP__ . V('o:SYS/CTL_DIR') . __SEP__ . $file);
			break;
			case 'mod':
				return file_exists(__APP__ . V('o:SYS/MOD_DIR') . __SEP__ . $file);
			break;
			case 'view':
				return file_exists(__APP__ . V('o:SYS/VIEW_DIR') . __SEP__ . $file);
			break;
			case 'site':
				return file_exists(__ROOT__ . $file);
			break;
			case 'sys':
			default:
				return file_exists($file);
		}
	}
}
/**
 *  类控制器默认函数
 */

class Ctl {
	var $validate = array();
	
	function Ctl() {
		$GLOBALS['TPL'] = array();
	}
	
	function validate($validate) {
		$this->validate = explode('|', $validate);
		foreach ($this->validate as $vali) {
			if ($vali = trim($vali)) {
				call_user_func_array(array(
					$this,
					'_' . $vali
				) , array());
			}
		}
	}
	
	function _csrf() {
		$csrf_type = V('o:csrf_type', 'once_token');
		if ($csrf_type == 'once_token') {
			$index = 0;
			if (!(url_csrf_check($index))) {
				echo 'csrf or re_post error';
				exit(-1);
			}
			else {
				if (url_csrf_pop($index)) {
					echo 'do_real_thing';
				}
				else {
					exit(-1);
				}
			}
		}
		elseif ($csrf_type == 'session_id') {
			//only check the csrf == session_id
			
		}
	}
}
/*
 * class APP
*/

class APP {
	static $_preActionArr = array();
	
	function APP() {
		APP::$_preActionArr['m'] = array();
		APP::$_preActionArr['f'] = array();
	}
	/**
	 *  URL 输出
	 */
	
	function URL($router, $queries = NULL) {
		return url_add_query(__WEB_ROOT__ . '?' . V('o:SYS/ROUTER_CONTR') . '=' . $router, $queries);
	}
	/**
	 *  $type m|f
	 *  $model  支持取反操作，！打头表示除了这些之外
	 *  支持*操作 表示所有子aaction
	 */
	
	function addPreAction($model, $type, $ctrlArr) {
		$runningRouter = APP::getRunningRouter();
		if (!((substr($model, 0, 1) != '!') ^ is_match_array($runningRouter, $ctrlArr))) {
			$model = trim(strtr($model, '!', ' '));
			APP::$_preActionArr[$type][$model] = $runningRouter;
		}
		//var_dump(APP::$_preActionArr);
		
	}
	
	function doPreAction() {
		foreach (APP::$_preActionArr as $type => $actions) {
			$t = substr($type, 0, 1);
			switch ($t) {
				case 'm':
					foreach ($actions as $mod => $ctl) {
						//var_dump($mod,substr($type,1,strlen($type)));
						DS($mod, substr($type, 1, strlen($type)));
					}
				break;
				case 'f': ///todo
					
				break;
			}
		}
	}
	
	function addAfrAction() {
	}
	/**
	 *  显示错误页，$default为是否使用服务器默认错误页，发送错误码
	 */
	
	function Err($errcode, $default = FALSE) {
		if ($default) {
			echo $errcode;
		}
		else {
			TPL::error($errcode);
		}
	}
	
	function ADP($type, $subType = NULL) {
		//
		static $AD = array();
		$st_type = $type;
		if (isset($subType)) {
			$st_type.= '/{$subType}';
		}
		if (isset($AD[$st_type])) {
			return $AD[$st_type];
		}
		$support_type = array(
			'db',
			'cache',
			'http',
			'serialization',
			'image'
		);
		if (in_array($type, $support_type)) {
			$ad_conf = V('o:adapter/' . $type);
			if (isset($subType) && isset($ad_conf[$subType])) {
				$_cls = $subType;
				$_conf = $ad_conf[$subType];
			}
			elseif (!empty($ad_conf)) {
				$_cls = array_shift(array_keys($ad_conf));
				$_conf = $ad_conf[$_cls];
			}
			$cls = sprintf(V('o:SYS/ADP_CLASS_NAME_FORMAT') , $_cls);
			if (!class_exists($cls)) {
				require_once (APP::__getInc($type . __SEP__ . $_cls . V('o:EXT/ADP') , 'adp'));
			}
			$obj = APP::O($cls);
			$obj->adp_init($_conf);
			return $obj;
		}
		else {
			throw new ADPException($type);
		}
	}
	/**
	 *  init
	 *  系统初始话代码
	 */
	
	function init() {
		APP::_init_sys_define(V('o:NEED_DEFINE'));
		//protocol
		list($protocol, $version) = explode('/', V('s:SERVER_PROTOCOL'));
		$httpDefaultPort = 80;
		$port = V('s:SERVER_PORT', $httpDefaultPort);
		if ($port == $httpDefaultPort) $portPart = '';
		else $portPart = ":" . $port;
		$host = V('s:HTTP_HOST');
		$uri = explode('?', V('s:REQUEST_URI') , 2);
		define('__BASE_URI__', strtolower($protocol) . '://' . $host . $portPart . $uri[0]);
		define('__WEB_ROOT__', $uri[0]);
		//var_dump(__BASE_URI__);
		
		//protocol
		
		//XDEBUG init
		if (defined('IS_XDEBUG') && IS_XDEBUG) {
			setcookie('XDEBUG_SESSION_START', 1);
		}
		else {
			if (isset($_COOKIE['XDEBUG_SESSION_START'])) {
				unset($_COOKIE['XDEBUG_SESSION_START']);
			}
		}
		///系统默认的日志位置
		define("SYS_DEFAULT_LOG_PATH", __VAR__ . 'logs' . __SEP__ . date('Y-m-d'));
		///预处理模块
		APP::doPreAction();
	}
	
	/**
	  *  程序析构函数，做垃圾处理，包括日志处理 
	  */
	function dest(){
		
	}
	/**
	 * F();
	 * 调用一个库方法我文件
	 * @param
	 * @return
	 */
	
	function F($type = 'app', $funName) {
		switch ($type) {
			case 'ct':
				require_once (__ROOT__ . $GLOBALS['SYS']['CTPHP_DIR'] . __SEP__ . 'libs' . __SEP__ . 'function' . __SEP__ . $funName . V('o:EXT/FUNC'));
			break;
			case 'app':
				require_once (__ROOT__ . $GLOBALS['SYS']['SITE_DIR'] . __SEP__ . 'libs' . __SEP__ . 'function' . __SEP__ . $funName . V('o:EXT/FUNC'));
			break;
		}
		$args = func_get_args();
		array_shift($args);
		array_shift($args);
		return call_user_func_array($funName, $args);
	}
	/**
	 * N($cls);
	 * 创建一个类实例 有问题
	 * @param $cls	     detail
	 * @return
	 */
	
	function N($cls) {
		if (class_exists($cls)) {
			if (is_callable("{$cls}::{$cls}")) {
				return call_user_func_array(array(
					$cls,
					$cls
				) , func_get_args());
			}
			elseif (is_callable("{$cls}::__construct")) {
				return call_user_func_array(array(
					$cls,
					'__construct'
				) , func_get_args());
			}
			else {
				$args = func_get_args();
				array_shift($args);
				//var_dump($cls);
				if (!empty($args)) {
					return new $cls($args[0]);
				}
				return new $cls();
			}
		}
		return FALSE;
	}
	/**
	 * O($cls);
	 * 单例创建一个类实例
	 * @param $cls	     detail
	 * @return
	 */
	
	function O($cls) {
		if (!isset($GLOBALS['CLS'])) {
			$GLOBALS['CLS'] = array();
		}
		if (isset($GLOBALS['CLS'][$cls])) {
			return $GLOBALS['CLS'][$cls];
		}
		$GLOBALS['CLS'][$cls] = APP::N($cls);
		return $GLOBALS['CLS'][$cls];
	}
	/**
	 * R();
	 *
	 * @param
	 * @return
	 */
	
	function R() {
	}
	///handler request
	
	function request() {
		APP::__require();
	}
	/**
	 * V();
	 *
	 * @param
	 * @return
	 */
	
	function V($k = NULL, $dv = NULL, $setVal = NULL) {
		static $v = array();
		$args = func_get_args();
		$key = trim(array_shift($args));
		$dv = array_shift($args);
		$value = array_shift($args);
		if (array_key_exists($key, $v) && $v[$key] !== NULL) {
			if (isset($setVal)) $v[$key] = $setVal;
			return $v[$key];
		}
		$all = array(
			'g' => $_GET,
			'p' => $_POST,
			's' => $_SERVER,
			'c' => $_COOKIE,
			'e' => isset($_SESSION) ? $_SESSION : array() ,
			'o' => $GLOBALS,
			'n' => $_ENV,
			'r' => $_REQUEST,
			'f' => $_FILES
		);
		//var_dump($key);
		list($k1, $k2) = preg_split("/:/", $key);
		if (isset($k1) && isset($k2) && isset($all[$k1]) && isset($all[$k1][$k2])) {
			$v[$key] = $all[$k1][$k2];
			if (isset($setVal)) $v[$key] = $setVal;
			return $v[$key];
		}
		else {
			$gg = preg_split('/\//', $k2);
			if (count($gg) == 2 && isset($all[$k1][$gg[0]][$gg[1]])) {
				$v[$key] = $all[$k1][$gg[0]][$gg[1]];
				if (isset($setVal)) {
					$v[$key] = $setVal;
					switch ($k1) {
							//case 'e':
							
							//	$_SESSION[]
							
					}
				}
				return $v[$key];
			}
		}
		return $dv;
	}
	
	function __getInc($ctl, $type = 'ctl') {
		switch ($type) {
			case 'ctl':
				return __APP__ . V('o:SYS/CTL_DIR') . __SEP__ . $ctl;
			break;
			case 'mod':
				return __APP__ . V('o:SYS/MOD_DIR') . __SEP__ . $ctl;
			break;
			case 'view':
				return __APP__ . V('o:SYS/VIEW_DIR') . __SEP__ . $ctl;
			break;
			case 'adp':
				return __CT__ . 'libs' . __SEP__ . V('o:SYS/ADP_DIR') . __SEP__ . $ctl;
		}
	}
	
	function __className($ctl, $type = 'ctl') {
		if ($type == 'ctl') {
			$__tmp = sprintf(V('o:SYS/CTL_CLASS_NAME_FORMAT') , ucfirst($ctl));
		}
		elseif ($type == 'mod') {
			$__tmp = sprintf(V('o:SYS/MOD_CLASS_NAME_FORMAT') , ucfirst($ctl));
		}
		if (class_exists($__tmp)) return $__tmp;
		return FALSE;
	}
	/**
	 * var_dump($matches);
	 type g s r
	 arg1 作为缓存参数的第一个参数
	 num 使用几个参数作为缓存参数
	 time 缓存时间
	 g1/300
	 */
	
	function __parseCacheType($cache) {
		if ($cache) {
			$exp = "/^(?<type>[gsr]?)((?<start>\d*):?(?<num>\d*))\/*(?<time>\d*)$/";
			if (!preg_match($exp, $cache, $matches)) return FALSE;
			return array(
				'type' => $matches['type'] ? APP::__parseCacheTypeOfDefine($matches['type']) : TYPE_CACHE_GLOBAL,
				'start' => $matches['start'] ? $matches['start'] : 0,
				'num' => $matches['num'] ? $matches['num'] : 0,
				'time' => $matches['time'] ? $matches['time'] : 0
			);
		}
	}
	
	function __parseCacheTypeOfDefine($str) {
		switch ($str) {
			case 's':
				return TYPE_CACHE_SESSION;
			case 'r':
				return TYPE_CACHE_RUNTIME;
			case 'g':
				return TYPE_CACHE_GLOBAL;
			default:
				return NULL;
		}
	}
	/**
	 *  数据集缓存清楚
	 */
	
	function DD($router, $cache = NULL) {
		$runtimeArr = 'CACHE';
		isset($GLOBAL[$runtimeArr]) ? $GLOBAL[$runtimeArr] = array() : NULL;
		$sessionArr = 'CACHE';
		isset($_SESSION[$sessionArr]) ? $_SESSION[$sessionArr] = array() : NULL;
		list($dir, $cls, $fun) = APP::__parseRouter($router, 'mod');
		$arr = APP::__parseCacheType($cache);
		if ($arr) list($type, $start, $num, $time) = array_values($arr);
		else return FALSE;
		$args = func_get_args();
		array_shift($args);
		array_shift($args);
		$cachekey = APP::__parseCacheKey($router, array_splice($args, $start, $num));
		switch ($type) {
			case TYPE_CACHE_SESSION:
				$_SESSION[$sessionArr][$cachekey] = NULL;
			break;
			case TYPE_CACHE_RUNTIME:
				$GLOBAL[$runtimeArr][$cachekey] = NULL;
			break;
			case TYPE_CACHE_GLOBAL:
				CACHE::del($cachekey);
			default:
		}
}
/**
 *  $cache 'g1/300' 'g1:3/300' 'g' 'g1'
 *  g/s/r
 *  g:cache 全局缓冲
 *  s:session缓存
 *  r:全局变量缓存，本次请求有效 存储在static变量中
 *
 */

function DS($router, $cache = NULL) {
	$runtimeArr = 'CACHE';
	isset($GLOBAL[$runtimeArr]) ? $GLOBAL[$runtimeArr] = array() : NULL;
	$sessionArr = 'CACHE';
	isset($_SESSION[$sessionArr]) ? $_SESSION[$sessionArr] = array() : NULL;
	list($dir, $cls, $fun) = APP::__parseRouter($router, 'mod');
	$arr = APP::__parseCacheType($cache);
	if (is_array($arr)) {
		list($type, $start, $num, $time) = array_values($arr);
		$args = func_get_args();
		array_shift($args);
		array_shift($args);
		$cachekey = APP::__parseCacheKey($router, array_splice($args, $start, $num));
	}
	else if ($arr === NULL) {
		$type = TYPE_CACHE_NO;
	}
	else return FALSE;
	//先尝试获取数据
	switch ($type) {
		case TYPE_CACHE_SESSION:
			$ret = V('e:' . $sessionArr . '/' . $cachekey, FALSE);
		break;
		case TYPE_CACHE_RUNTIME:
			$ret = CK($GLOBAL[$runtimeArr], $cachekey);
		break;
		case TYPE_CACHE_GLOBAL:
			$ret = CACHE::get($cachekey);
		case TYPE_CACHE_NO:
		default:
			$ret = FALSE;
	}
	if ($ret) return $ret;
	//w为获取到数值，从数据组件中无缓存获取
	if (CT_WARP::file_exists($dir . __SEP__ . $cls . V('o:EXT/MOD') , 'mod')) {
		require_once (APP::__getInc($dir . __SEP__ . $cls . V('o:EXT/MOD') , 'mod'));
		$__cls = APP::__className($cls, 'mod');
		if ($__cls !== FALSE) {
			$__obj = APP::O($__cls);
			if (is_callable(array(
				$__obj,
				$fun
			))) {
				$args = func_get_args();
				array_shift($args);
				array_shift($args);
				$ret = call_user_func_array(array(
					$__obj,
					$fun
				) , $args);
			}
		}
	}
	//对数据进行缓存
	switch ($type) {
		case TYPE_CACHE_SESSION:
			//w未实现好V的设置方法
			
			//$ret=V('e:'.$sessionArr.'/'.$cachekey,FALSE);
			$_SESSION[$sessionArr][$cachekey] = $ret;
		break;
		case TYPE_CACHE_RUNTIME:
			//缓存时间值无效
			$GLOBAL[$runtimeArr][$cachekey] = $ret;
		break;
		case TYPE_CACHE_GLOBAL:
			CACHE::set($cachekey, $ret, $time);
		default:
	}
	return $ret;
}

function __parseCacheKey($router, $keys) {
	return md5($router . serialize($keys));
}

function _init_sys_define($arr) {
	$SYS_DEFINE_BEGIN = 123;
	$SYS_DEFINE_HEAD = '#';
	$SYS_DEFINE_END = '#';
	foreach ($arr as $val) {
		define($val, $SYS_DEFINE_HEAD . ($SYS_DEFINE_BEGIN++) . $SYS_DEFINE_END);
	}
}

function getRunningRouter($retStr = TRUE) {
	static $routerArr = NULL;
	static $routerStr = NULL;
	if ($routerStr === NULL) {
		$router = V('g:m');
		$routerArr = APP::__parseRouter($router);
		$routerStr = $routerArr[0] . '/' . $routerArr[1] . '.' . $routerArr[2];
	}
	return $retStr ? $routerStr : $routerArr;
}

function __require($router = FALSE) {
	$router = $router ? $router : APP::getRunningRouter();
	list($dir, $ctl, $action) = APP::__parseRouter($router);
	//var_dump($dir, $ctl, $action);
	if (CT_WARP::file_exists($dir . __SEP__ . $ctl . V('o:EXT/CTL') , 'ctl')) {
		require_once (APP::__getInc($dir . __SEP__ . $ctl . V('o:EXT/CTL')));
		$__cls = APP::__className($ctl);
		if ($__cls !== FALSE) {
			$__obj = APP::O($__cls);
			if (is_callable(array(
				$__obj,
				$action
			))) {
				return call_user_func(array(
					$__obj,
					$action
				));
			}
			else {
				APP::Err(404);
				//error
				
			}
		}
		else {
			APP::Err(404);
			//error
			
		}
	}
	else {
		APP::Err(404);
		//error
		
	}
}
/**
 * parseRouter();
 *
 * @param
 * @return
 */

function __parseRouter($router = FALSE, $type = 'ctl') {
	switch ($type) {
		case 'ctl':
			$def = V('o:SYS/DEFAULT_ACTION');
		break;
		case 'mod':
			$def = V('o:SYS/DEFAULT_MODEL');
		break;
	}
	//var_dump($router);
	if (preg_match("/^([\w-_\/]*\/)?([\w_]+)\.?(\S*)$/i", $router, $matchs)) {
		array_shift($matchs);
		$r = array_compression($matchs);
		//var_dump($r);
		if (count($r) == 1) {
			$dir = '';
			$ctl = $r[1];
			$action = $def;
		}
		elseif (count($r) == 2) {
			if (isset($r[0])) {
				$dir = $r[0];
				$ctl = $r[1];
				$action = $def;
			}
			else {
				$dir = '';
				$ctl = $r[1];
				$action = $r[2];
			}
		}
		elseif (count($r) == 3) {
			$dir = $r[0];
			$ctl = $r[1];
			$action = $r[2];
		}
		else {
			if ($type == 'ctl') return APP::__parseRouter(DEFAULT_ROUTER);
			else return NULL;
		}
		$ret = array(
			'dir' => $dir,
			'ctl' => $ctl,
			'action' => $action
		);
		//var_dump($ret);
		if ($type == 'ctl') {
			$GLOBALS['RUNNING']['NowRouter'] = $ret;
		}
		return array_values($ret);
	}
}
}
/*
 * class TPL
 * 模板类
*/

class TPL {
	static $_scriptData = array();
	
	function header(){
		
	}
	
	///https://developer.mozilla.org/en/http_access_control
	function headerACLOrigin($orgin='*'){
		header('Access-Control-Allow-Origin: '.$orgin.'');
	}
	
	function JSONP($callback, $data) {
		return sprintf("<script type='text/javascript'>%s(%s);</script>", $callback, json_encode($data));
	}
	///使用window.name属性实现跨域消息
	function CSNAME($data){
		return sprintf("<script type='text/javascript'>window.name='%s'</script>",json_encode($data));
	}
	
	function AjaxRst() {
	}
	/**
	 *  j将对象数组以json格式，script方式传给客户端
	 */
	
	function assignScript($mixed, $val = NULL) {
		if (is_string($mixed)) {
			TPL::$_scriptData[$mixed] = $val;
		}
		else {
			foreach ($mixed as $key => $val) {
				if (!privete_key($key)) {
					if ($val === NULL) $val = '';
					TPL::$_scriptData[$key] = $val;
				}
			}
		}
	}
	/**
	 *  脚本输出数据，用于和前端js 通信
	 */
	
	function _scriptData() {
		//$initDataFunction='ct.initData';
		$initDataString = 'initData';
		if (!empty(TPL::$_scriptData)) {
			return sprintf("<script id='initDiv' type='text/javascript'>%s=%s;</script>", $initDataString, json_encode(TPL::$_scriptData));
		}
	}
	/**
	 * assign($key,$val);
	 * Brief
	 * @param $key,$val
	 * @return
	 */
	
	function assign($key, $val) {
		$GLOBALS['TPL'][$key] = $val;
	}
	/**
	 *  css链接方法
	 *
	 */
	
	function linkcss($file = FALSE) {
		if (is_string($file)) {
			echo sprintf('<link href="%s/%s.css" type="text/css" rel="stylesheet" />', __WEB_ROOT__ . V('o:SYS/CSS_DIR') , $file);
		}
		elseif (is_array($file)) {
			foreach ($file as $f) {
				TPL::linkcss($f);
			}
		}
	}
	
	function linkjs($file = FALSE,$rand=FALSE) {
		if (is_string($file)) {
			if($rand||(defined('IS_DEBUG')&&IS_DEBUG)){
				$rand="?_rand=".rand();
			}
			echo sprintf('<script src="%s/%s.js%s" type="text/javascript"></script>', __WEB_ROOT__ . V('o:SYS/JS_DIR') , $file,$rand);
		}
		elseif (is_array($file)) {
			foreach ($file as $f) {
				TPL::linkjs($f);
			}
		}
	}
	
	function linkjsBase() {
		TPL::linkjs(V('o:SYS/JS_BASE'));
	}
	
	function linkcssBase() {
		TPL::linkcss(V('o:SYS/CSS_BASE'));
	}
	/**
	  *  用于s输出对话框中使用到iframe时的标准容器 
	  */
	function _loadiframe(){
		$_loadimg='<img id="load-img" style="display:none" src="/app/images/loading.gif"/>';
		$_iframe="<iframe style='display:none' id='loadiframe'></iframe>";
		$_script='<script type="text/javascript">$("iframe").load(function(){$("#load-img").hide("slow");$(this).show();});</script>';
		return $_loadimg.$_iframe.$_script;
	}
	/**
	 *  title 标题
	 */
	
	function title($title) {
		echo sprintf('<title>%s</title>', $title);
	}
	
	/**
	  *  meta 
	  */
	function meta(){
		
	}
	
	/**
	  *  favicon
	  */
	function favicon($icon){
		echo sprintf('<link rel="shortcut icon" href="/%s" />',$icon);
	}
	
	function error($errcode){
		TPL::display('common/error.'.$errcode);
	}
	
	/**
	 * display();
	 *
	 * @param
	 * @return
	 */
	
	function display($view = NULL) {
		header('Content-Type: text/html; charset=UTF-8');
		if ($view == NULL) {
			$view = $GLOBALS['RUNNING']['NowRouter'];
		}
		else {
			//$view='common/pub.index'
			if (strrpos($view, '/') === FALSE) {
				$dir = '';
				$str = $view;
			}
			else {
				$str = split('/', $view);
				$dir = $str[0];
				$str = $str[1];
			}
			if (strpos($str, '.') === FALSE) {
				$ctl = $str;
				$action = V('o:SYS/DEFAULT_ACTION');
			}
			else {
				$str = split('\.', $str);
				$ctl = $str[0];
				$action = $str[1];
			}
			$view = array(
				'dir' => $dir,
				'ctl' => $ctl,
				'action' => $action
			);
		}
		extract($GLOBALS['TPL'], EXTR_SKIP);
		$viewFile = APP::__getInc($view['dir'] . __SEP__ . $view['ctl'] . __SEP__ . $view['action'] . V('o:EXT/VIEW') , 'view');
		if (file_exists($viewFile)) {
			echo '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">', '<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">';
			require_once ($viewFile);
			echo TPL::_scriptData();
			echo TPL::_loadiframe();
			echo '</html>';
		}
		else {
			trigger_error("{$viewFile} is not existed");
		}
	}
}
/**
 * ();
 *
 * @param
 * @return
 */

function R() {
	APP::R();
}

function V() {
	return call_user_func_array(array(
		'APP',
		'V'
	) , func_get_args());
}

function DS() {
	return call_user_func_array(array(
		'APP',
		'DS'
	) , func_get_args());
}

function DD() {
	return call_user_func_array(array(
		'APP',
		'DD'
	) , func_get_args());
}
/**
 *  调用一个在app/libs/function/没目录 的函数文件
 */

function FI() {
	$args = func_get_args();
	array_unshift($args, 'app');
	call_user_func_array(array(
		'App',
		'F'
	) , $args);
}
//$v=&function_alias('a');

//$v();

/**
 *  调用一个在ct/libs/function/没目录 的函数文件
 */

function FO() {
	$args = func_get_args();
	array_unshift($args, 'ct');
	call_user_func_array(array(
		'App',
		'F'
	) , $args);
}
/**
 *  没默认F函数调用FO为调用内部公共函数文件
 */

function F() {
	call_user_func_array('FO', func_get_args());
}

function F_() {
	call_user_func_array('FI', func_get_args());
}
/**
 *  创建一个app下的单例的对象
 */

function CIO($clsName) {
	$GLOBALS['CLASS_DIR_NOW'] = __ROOT__ . $GLOBALS['SYS']['SITE_DIR'] . __SEP__ . 'libs' . __SEP__ . 'class' . __SEP__;
	if (!class_exists($clsName)) require_once ($GLOBALS['CLASS_DIR_NOW'] . $clsName . V('o:EXT/CLS'));
	return APP::O($clsName);
}
/**
 *  创建一个app下的对象
 */

function CIN($clsName) {
	$GLOBALS['CLASS_DIR_NOW'] = __ROOT__ . $GLOBALS['SYS']['SITE_DIR'] . __SEP__ . 'libs' . __SEP__ . 'class' . __SEP__;
	if (!class_exists($clsName)) require_once ($GLOBALS['CLASS_DIR_NOW'] . $clsName . V('o:EXT/CLS'));
	return APP::N($clsName);
}
/**
 *  创建一个ct下的单例的对象
 */

function COO($clsName) {
	$GLOBALS['CLASS_DIR_NOW'] = __ROOT__ . $GLOBALS['SYS']['CTPHP_DIR'] . __SEP__ . 'libs' . __SEP__ . 'class' . __SEP__;
	if (!class_exists($clsName)) require_once ($GLOBALS['CLASS_DIR_NOW'] . $clsName . V('o:EXT/CLS'));
	return APP::O($clsName);
}
/**
 *  创建一个ct下的对象
 */

function CON($clsName) {
	$GLOBALS['CLASS_DIR_NOW'] = __ROOT__ . $GLOBALS['SYS']['CTPHP_DIR'] . __SEP__ . 'libs' . __SEP__ . 'class' . __SEP__;
	if (!class_exists($clsName)) require_once ($GLOBALS['CLASS_DIR_NOW'] . $clsName . V('o:EXT/CLS'));
	return call_user_func_array(array(
		'APP',
		'N'
	) , func_get_args());
	//return APP::N($clsName);
	
}

function N() {
	return call_user_func_array('CON', func_get_args());
}

function O() {
	return call_user_func_array('COO', func_get_args());
}

function N_() {
	return call_user_func_array('CIN', func_get_args());
}

function O_() {
	return call_user_func_array('CIO', func_get_args());
}
/*
 * class UserBase
 * 当前登录用户信息几类
 * 该类x需要提供可插拔的方式来配置二次开发需要额外获取的信息
*/

class UserBase {
	var $_sid = NULL; //session_id
	var $guid = NULL;
	
	
	function UserBase() {
		if (!($sid = session_id())) {
			session_start();
			$sid = session_id();
		}
		$this->_sid = $sid;
	}
	/**
	 *  客户浏览器端信息
	 *  ip/brower/geo/
	 *  brower：ismobile,isModelMobile,engine,$fac,$version,$isie,
	 *  referer
	 *  callmethod:default/ajax/server_api/js_api/
	 */
	
	function _getInfoFromBrower() {
		static $info = array();
		if (empty($info)) {
			$info['ip'] = get_client_ip();
		}
	}
	/**
	 *  从存储设备中获取用户信息
	 *  visit_rate 访问频度
	 */
	
	function _getInfoFromStore() {
	}
	/**
	 *  综合 判断SESSION['USER'] guid数据
	 */
	
	function isLogin() {
		return !!V('e:USER/guid', FALSE);
	}
	/**
	 *  会话id
	 */
	
	function sid() {
		return V('e:USER/_sid', FALSE);
	}
	
	function login() {
		if (isset($_SESSION['USER'])) {
			$_SESSION['USER'] = array();
		}
		else {
			if (!session_id()) {
				session_start();
			}
			$_SESSION['USER']['guid'] = unique();
		}
	}
	
	function logout() {
		if (isset($_SESSION['USER']) && isset($_SESSION['USER']['guid'])) {
			unset($_SESSION['USER']['guid']);
			return TRUE;
		}
		return FALSE;
	}
	
	function getUserInfo() {
	}
	
	function getUserID() {
	}
	
	function setUserInfo() {
	}
}
/**
 *  支持 不同类型的输出
 *  浏览器、标准errout、firebug、文件、OS日志输出
 *
 */
define("L_ERROR", 1);
define("L_WARNING", 2);
define("L_MESSAGE", 3);

class Logger {
	var $loggerBuf = array();
	var $logPath = NULL; //支持日期序列化，暂不支持变量名序列化
	var $isEndEcho = TRUE; //如果是文件操作的话，是否将输出在j脚本执行完后一并输出
	var $outputType = 'file';
	var $fobj = NULL;
	var $firephp = NULL;
	/**
	 *  $config outputType:browser|file|os|firebug|stderr
	 *  if is file	 filepath and isEndEcho will be sent
	 *
	 */
	
	function Logger($config) {
		if (isset($config['outputType'])) {
			$this->outputType = $config['outputType'];
			switch ($config['outputType']) {
				case 'file':
					$this->logPath = isset($config['filepath']) ? $config['filepath'] : SYS_DEFAULT_LOG_PATH;
					$this->isEndEcho = isset($config['isEndEcho']) ? $config['isEndEcho'] : TRUE;
					$this->fobj = APP::ADP('file');
				case 'browser':
				break;
				case 'os':
				break;
				case 'firebug':
					require_once (__PLU__ . FirePHPCore . __SEP__ . "FirePHP.class.php");
					$this->firephp = FirePHP::getInstance(TRUE);
				break;
				case 'stderr':
				break;
			}
		}
	}
	
	function _log($msg, $args, $logType = L_MESSAGE) {
		$logs = "";
		switch ($this->outputType) {
			case 'file':
				if ($this->isEndEcho) {
					$this->loggerBuf[] = $logs;
				}
				else {
					$this->fobj->append($this->logPath, $logs);
				}
			break;
			case 'browser':
			break;
			case 'os':
			break;
			case 'firebug':
				switch ($logType) {
					case L_ERROR:
						$this->firephp->error($args, $msg); //可能支持不只这个方法
						
					break;
					case L_MESSAGE:
						$this->firephp->log($args, $msg); //可能支持不只这个方法
						
					break;
					case L_WARNING:
						$this->firephp->warn($args, $msg); //可能支持不只这个方法
						
					break;
				}
			break;
			case 'stderr':
			break;
		}
	}
	
	function error() {
		$args = fun_get_args();
		array_unshift($args, L_ERROR);
		call_user_func_array(array(
			$this,
			'_log'
		) , $args);
	}
	
	function warn($msg) {
		$args = fun_get_args();
		array_unshift($args, L_WARNING);
		call_user_func_array(array(
			$this,
			'_log'
		) , $args);
	}
	
	function log($msg) {
		$args = fun_get_args();
		array_unshift($args, L_MESSAGE);
		call_user_func_array(array(
			$this,
			'_log'
		) , $args);
	}
	/**
	 *  仅在s输出方式是文件，脚本执行完毕输出时才有效
	 */
	
	function dumpLog() {
		if ($this->isEndEcho) {
			$this->fobj->append($this->logPath, $this->loggerBuf);
		}
	}
}

class Cache {
	
	function getInstance() {
		return APP::ADP('cache');
	}
	//------------------------------------------------------------------
	
	function &instance() {
		static $c;
		if (empty($c)) {
			$c = APP::ADP('cache');
		}
		return $c;
	}
	
	function get() {
		return call_user_func_array(array(
			Cache::instance() ,
			'get'
		) , func_get_args());
	}
	
	function set() {
		return call_user_func_array(array(
			Cache::instance() ,
			'set'
		) , func_get_args());
	}
	
	function del() {
		return call_user_func_array(array(
			Cache::instance() ,
			'del'
		) , func_get_args());
	}
}

class ArgException extends Exception {
	
	function __toString() {
		return get_class($this) . ':' . "{$this->message},{$this->file},{$this->line}\n";
	}
}

class ADPException extends Exception {
	
	function __toString() {
		return "------------ADP " . $this->message . " is not support!\n";
	}
}

class HELP {
}

class HTML extends HELP {
	var $csrf = FALSE;
	var $auto_echo = TRUE; //自动输出，无需echo
	
	function HTML($conf = array()) {
		$this->csrf = isset($conf['csrf']) ? $conf['csrf'] : FALSE;
		$this->auto_echo = isset($conf['auto_echo']) ? $conf['auto_echo'] : TRUE;
	}
	
	function form($action = '', $inputs = array() , $id = 'form', $submitTitle = 'submit', $method = 'get', $withRest = False, $class = 'default_form') {
		$inputstr = '';
		if (!empty($inputs)) {
			foreach ($inputs as $conf) {
				$inputstr.= $this->input($conf['type'], $conf['name'], $conf['value'], $conf['title']);
			}
		}
		if ($this->csrf && $action != '') {
			$action = url_csrf_push($action);
		}
		$reset = $withRest ? "<input type='reset' value='" . $withRest . "'/>" : '';
		$rst = sprintf("<form method='%s' action='%s' id='%s' class='%s'>%s<input type='submit' value='%s'/>%s</form>", $method, $action, $id, $class, $inputstr, $submitTitle, $reset);
		if ($this->auto_echo) {
			echo $rst;
			return;
		}
		return $rst;
	}
	
	function input($type, $name, $value, $title) {
		return sprintf("<label for='%s'>%s:</label><input type='%s' value='%s' name='%s' id='%s'/>", $name, $title, $type, $value, $name, $name);
	}
}
?>